package cn.agrael.struts.plugin.ejb3;

import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;

import javax.annotation.PostConstruct;
import javax.annotation.PreDestroy;
import javax.interceptor.Interceptors;

/**
 * bean 的 ejb相关 注解信息。
 * 
 * @author <a href="mailto:agraellee@gmail.com">Agrael·Lee</a>
 * 
 */
public class BeanEJBAnnotation {

	/** {@link PostConstruct} 对应的方法 */
	private Method postConstructAnnotationMethod;

	/** {@link PreDestroy} 对应的方法 */
	private Method preDestroyAnnotationMethod;

	/** 类级别 {@link Interceptors} 对应的包装器 */
	private InterceptorsAnnotationWrapper classInterceptors;

	/** 方法级别 {@link Interceptors} 对应的包装器印射 */
	private Map<String, InterceptorsAnnotationWrapper> methodInterceptors = new HashMap<String, InterceptorsAnnotationWrapper>();

	/** 类级别资源注入信息包装器 */
	private ClassInjectAnnotationWrapper classInject;

	/** 方法资源注入信息包装器印射 */
	private Map<String, MethodInjectAnnotationWrapper> methodInjects = new HashMap<String, MethodInjectAnnotationWrapper>();

	/** 字段资源注入信息包装器印射 */
	private Map<String, FieldInjectAnnotationWrapper> fieldInjects = new HashMap<String, FieldInjectAnnotationWrapper>();

	/** 如果所有信息都为默认，则该值为 true ，且认为该 BeanEJBAnnotation 为空 */
	private boolean isEmpty = true;

	/**
	 * 得到 {@link PostConstruct} 对应的方法。
	 * 
	 * @return {@link PostConstruct} 对应的方法。
	 */
	public Method getPostConstructAnnotationMethod() {
		return this.postConstructAnnotationMethod;
	}

	/**
	 * 设置 {@link PostConstruct} 对应的方法。
	 * 
	 * @param postConstructAnnotationMethod {@link PostConstruct} 对应的方法。
	 */
	void setPostConstructAnnotationMethod(Method postConstructAnnotationMethod) {
		noEmpty();
		this.postConstructAnnotationMethod = postConstructAnnotationMethod;
	}

	/**
	 * 得到 {@link PreDestroy} 对应的方法 。
	 * 
	 * @return {@link PreDestroy} 对应的方法 。
	 */
	public Method getPreDestroyAnnotationMethod() {
		return this.preDestroyAnnotationMethod;
	}

	/**
	 * 设置 {@link PreDestroy} 对应的方法 。
	 * 
	 * @param preDestroyAnnotationMethod {@link PreDestroy} 对应的方法 。
	 */
	void setPreDestroyAnnotationMethod(Method preDestroyAnnotationMethod) {
		noEmpty();
		this.preDestroyAnnotationMethod = preDestroyAnnotationMethod;
	}

	/**
	 * 得到 类级别 {@link Interceptors} 对应的包装器。
	 * 
	 * @return 类级别 {@link Interceptors} 对应的包装器。
	 */
	public InterceptorsAnnotationWrapper getClassInterceptors() {
		return this.classInterceptors;
	}

	/**
	 * 设置 类级别 {@link Interceptors} 对应的包装器。
	 * 
	 * @param classInterceptors 类级别 {@link Interceptors} 对应的包装器。
	 */
	void setClassInterceptors(InterceptorsAnnotationWrapper classInterceptors) {
		noEmpty();
		this.classInterceptors = classInterceptors;
	}

	/**
	 * 得到 方法级别 {@link Interceptors} 对应的包装器印射。
	 * 
	 * @return 方法级别 {@link Interceptors} 对应的包装器印射。
	 */
	public Map<String, InterceptorsAnnotationWrapper> getMethodInterceptors() {
		return this.methodInterceptors;
	}

	/**
	 * 得到 方法资源注入信息包装器印射。
	 * 
	 * @return 方法资源注入信息包装器印射。
	 */
	public Map<String, MethodInjectAnnotationWrapper> getMethodInjects() {
		return this.methodInjects;
	}

	/**
	 * 得到 字段资源注入信息包装器印射。
	 * 
	 * @return 字段资源注入信息包装器引射。
	 */
	public Map<String, FieldInjectAnnotationWrapper> getFieldInjects() {
		return this.fieldInjects;
	}

	/**
	 * 添加一个 方法级别 {@link Interceptors} 对应的包装器 到该 BeanEJBAnnotation。
	 * 
	 * @param methodName 拦截器注解方法的 方法名。
	 * @param interceptorsAnnotationWrapper 拦截器注解对应的包装器。
	 */
	void addMethodInterceptor(String methodName, InterceptorsAnnotationWrapper interceptorsAnnotationWrapper) {
		noEmpty();
		this.methodInterceptors.put(methodName, interceptorsAnnotationWrapper);
	}

	/**
	 * 添加一个 字段资源注入信息包装器 到该 BeanEJBAnnotation。
	 * 
	 * @param fieldName 字段注入注解注解的字段的 字段名。
	 * @param injectAnnotationWrapper 注入注解对应的包装器。
	 */
	void addFieldInject(String fieldName, FieldInjectAnnotationWrapper injectAnnotationWrapper) {
		noEmpty();
		this.fieldInjects.put(fieldName, injectAnnotationWrapper);
	}

	/**
	 * 添加一个 方法资源注入信息包装器 到该 BeanEJBAnnotation。
	 * 
	 * @param methodName 方法注入注解注解的方法的 方法名。
	 * @param injectAnnotationWrapper 注入注解对应的包装器。
	 */
	void addMethodInject(String methodName, MethodInjectAnnotationWrapper injectAnnotationWrapper) {
		noEmpty();
		this.methodInjects.put(methodName, injectAnnotationWrapper);
	}

	/**
	 * 得到 类级别资源注入信息包装器。
	 * 
	 * @return 类级别资源注入信息包装器。
	 */
	public InjectAnnotationWrapper getClassInject() {
		return this.classInject;
	}

	/**
	 * 设置 类级别资源注入信息包装器。
	 * 
	 * @param classInject 类级别资源注入信息包装器。
	 */
	void setClassInject(ClassInjectAnnotationWrapper classInject) {
		noEmpty();
		this.classInject = classInject;
	}

	/**
	 * 如果所有信息都为默认，则返回 true ，且认为该 BeanEJBAnnotation 为空。
	 * 
	 * @return 为空返回 true ，不为空返回 false。
	 */
	public boolean isEmpty() {
		return this.isEmpty;
	}

	void noEmpty() {
		this.isEmpty = false;
	}
}
